#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Python后端服务器
提供HTTP API接口，与Electron前端通信
"""
import signal
import sys
import json
import logging
from http.server import HTTPServer, BaseHTTPRequestHandler
from urllib.parse import urlparse
import threading
import time
from simion_runner import run_simion_automation, stop_simion_automation, get_simion_status
from i18n import set_language, t
from utils.logging import get_logger, get_log_queue
from utils.common import format_runtime, setup_console_encoding
import logging


SERVER_CONFIG = {
    'host': 'localhost',
    'port': 8888,
    'debug': True,
}

def load_from_env():
    """从环境变量加载配置"""
    import os
    if os.getenv('SERVER_HOST'):
        SERVER_CONFIG['host'] = os.getenv('SERVER_HOST')
    if os.getenv('SERVER_PORT'):
        SERVER_CONFIG['port'] = int(os.getenv('SERVER_PORT'))
    if os.getenv('DEBUG'):
        SERVER_CONFIG['debug'] = os.getenv('DEBUG').lower() == 'true'


logger = get_logger(__name__)
log_queue = get_log_queue()

# 禁用HTTP服务器的根日志记录器
logging.getLogger('http.server').setLevel(logging.CRITICAL)
logging.getLogger('http.server').disabled = True

# 禁用所有HTTP相关的日志记录器
logging.getLogger('urllib3').setLevel(logging.CRITICAL)
logging.getLogger('urllib3').disabled = True
logging.getLogger('requests').setLevel(logging.CRITICAL)
logging.getLogger('requests').disabled = True

# 设置控制台输出编码
setup_console_encoding()

class SimionAPIHandler(BaseHTTPRequestHandler):
    """SIMION API处理器"""
    
    def log_message(self, format, *args):
        """重写日志方法，完全禁用HTTP请求日志输出"""
        pass
    
    def do_OPTIONS(self):
        """处理CORS预检请求"""
        self.send_response(200)
        self.send_header('Access-Control-Allow-Origin', '*')
        self.send_header('Access-Control-Allow-Methods', 'GET, POST, PUT, DELETE, OPTIONS')
        self.send_header('Access-Control-Allow-Headers', 'Content-Type, Authorization')
        self.end_headers()
    
    def do_GET(self):
        """处理GET请求"""
        try:
            parsed_url = urlparse(self.path)
            path = parsed_url.path
            
            if path == '/':
                self.handle_test_page()
            elif path == '/status':
                self.handle_get_status()
            elif path == '/health':
                self.handle_health_check()
            elif path == '/logs':
                self.handle_get_logs()
            else:
                self.send_error(404, "Not Found")
        except Exception as e:
            logger.error(f"GET请求处理错误: {e}")
            self.send_error(500, "Internal Server Error")
    
    def do_POST(self):
        """处理POST请求"""
        try:
            parsed_url = urlparse(self.path)
            path = parsed_url.path
            
            if path == '/run':
                self.handle_run_automation()
            elif path == '/stop':
                self.handle_stop_automation()
            else:
                self.send_error(404, "Not Found")
        except Exception as e:
            logger.error(f"POST请求处理错误: {e}")
            self.send_error(500, "Internal Server Error")
    
    def handle_test_page(self):
        """处理测试页面请求"""
        try:
            html_content = """
<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>SIMION Python后端服务器测试页面</title>
    <style>
        body {
            font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
            margin: 0;
            padding: 20px;
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            color: white;
            min-height: 100vh;
        }
        .container {
            max-width: 800px;
            margin: 0 auto;
            background: rgba(255, 255, 255, 0.1);
            padding: 30px;
            border-radius: 15px;
            backdrop-filter: blur(10px);
            box-shadow: 0 8px 32px rgba(0, 0, 0, 0.3);
        }
        h1 {
            text-align: center;
            margin-bottom: 30px;
            font-size: 2.5em;
            text-shadow: 2px 2px 4px rgba(0, 0, 0, 0.3);
        }
        .status-card {
            background: rgba(255, 255, 255, 0.2);
            padding: 20px;
            margin: 15px 0;
            border-radius: 10px;
            border-left: 5px solid #4CAF50;
        }
        .api-section {
            margin: 30px 0;
        }
        .api-endpoint {
            background: rgba(0, 0, 0, 0.2);
            padding: 15px;
            margin: 10px 0;
            border-radius: 8px;
            font-family: 'Courier New', monospace;
        }
        .method {
            display: inline-block;
            padding: 4px 8px;
            border-radius: 4px;
            font-weight: bold;
            margin-right: 10px;
        }
        .get { background: #4CAF50; }
        .post { background: #FF9800; }
        .button {
            display: inline-block;
            padding: 10px 20px;
            background: #4CAF50;
            color: white;
            text-decoration: none;
            border-radius: 5px;
            margin: 5px;
            transition: background 0.3s;
        }
        .button:hover {
            background: #45a049;
        }
        .info {
            background: rgba(33, 150, 243, 0.2);
            padding: 15px;
            border-radius: 8px;
            margin: 15px 0;
        }
    </style>
</head>
<body>
    <div class="container">
        <h1>🚀 SIMION Python后端服务器</h1>
        
        <div class="status-card">
            <h2>✅ 服务器状态</h2>
            <p><strong>状态:</strong> 运行中</p>
            <p><strong>端口:</strong> 8000</p>
            <p><strong>时间:</strong> <span id="current-time"></span></p>
        </div>

        <div class="api-section">
            <h2>🔗 API端点</h2>
            
            <div class="api-endpoint">
                <span class="method get">GET</span>
                <strong>/status</strong> - 获取服务器状态
                <a href="/status" class="button">测试</a>
            </div>
            
            <div class="api-endpoint">
                <span class="method get">GET</span>
                <strong>/health</strong> - 健康检查
                <a href="/health" class="button">测试</a>
            </div>
            
            <div class="api-endpoint">
                <span class="method get">GET</span>
                <strong>/logs</strong> - 获取日志
                <a href="/logs" class="button">测试</a>
            </div>
            
            <div class="api-endpoint">
                <span class="method post">POST</span>
                <strong>/run</strong> - 运行SIMION自动化
            </div>
            
            <div class="api-endpoint">
                <span class="method post">POST</span>
                <strong>/stop</strong> - 停止SIMION自动化
            </div>
        </div>

        <div class="info">
            <h3>📋 功能说明</h3>
            <ul>
                <li><strong>SIMION自动化:</strong> 支持多线程频率扫描</li>
                <li><strong>工作空间管理:</strong> 自动创建和管理临时工作空间</li>
                <li><strong>多语言支持:</strong> 中文、日文、英文</li>
                <li><strong>实时日志:</strong> 支持实时查看运行日志</li>
                <li><strong>状态监控:</strong> 实时监控任务状态</li>
            </ul>
        </div>

        <div class="info">
            <h3>🛠️ 技术栈</h3>
            <ul>
                <li><strong>后端:</strong> Python HTTP Server</li>
                <li><strong>多线程:</strong> ThreadPoolExecutor</li>
                <li><strong>日志系统:</strong> 自定义QueueLogHandler</li>
                <li><strong>国际化:</strong> 自定义i18n模块</li>
                <li><strong>工具模块:</strong> utils包（logging, common）</li>
            </ul>
        </div>
    </div>

    <script>
        // 更新当前时间
        function updateTime() {
            const now = new Date();
            document.getElementById('current-time').textContent = now.toLocaleString('zh-CN');
        }
        updateTime();
        setInterval(updateTime, 1000);

        // 添加一些交互效果
        document.querySelectorAll('.button').forEach(button => {
            button.addEventListener('click', function(e) {
                if (this.textContent === '测试') {
                    e.preventDefault();
                    const url = this.getAttribute('href');
                    fetch(url)
                        .then(response => response.json())
                        .then(data => {
                            alert('API响应: ' + JSON.stringify(data, null, 2));
                        })
                        .catch(error => {
                            alert('请求失败: ' + error.message);
                        });
                }
            });
        });
    </script>
</body>
</html>
            """
            
            self.send_response(200)
            self.send_header('Content-type', 'text/html; charset=utf-8')
            self.end_headers()
            self.wfile.write(html_content.encode('utf-8'))
            
        except Exception as e:
            logger.error(f"测试页面处理错误: {e}")
            self.send_error(500, "Internal Server Error")

    def handle_get_status(self):
        """获取运行状态"""
        try:
            status = get_simion_status()
            self.send_json_response(status)
        except Exception as e:
            logger.error(f"获取状态失败: {e}")
            self.send_error(500, "Internal Server Error")
    
    def handle_health_check(self):
        """健康检查"""
        self.send_json_response({"status": "ok", "message": "Python后端服务正常运行"})
    
    def handle_get_logs(self):
        """获取日志"""
        try:
            logs = []
            # 获取队列中的所有日志
            while not log_queue.empty():
                try:
                    log_entry = log_queue.get_nowait()
                    logs.append(log_entry)
                except:
                    break
            
            self.send_json_response({"success": True, "logs": logs})
        except Exception as e:
            logger.error(f"获取日志失败: {e}")
            self.send_error(500, "Internal Server Error")
    
    def handle_run_automation(self):
        """运行SIMION自动化"""
        try:
            # 读取请求体
            content_length = int(self.headers['Content-Length'])
            post_data = self.rfile.read(content_length)
            config = json.loads(post_data.decode('utf-8'))
            
            # 设置语言
            language = config.get('language', 'zh-CN')
            set_language(language)
            
            # 在后台线程中运行自动化
            def run_in_background():
                try:
                    result = run_simion_automation(config)
                    # 统一使用INFO级别记录结果，包含运行时间
                    if result.get('success', False):
                        runtime = result.get('runtime_seconds', 0)
                        formatted_runtime = format_runtime(runtime)
                        logger.info(t('automation_completed') + f": {result}，运行时间: {formatted_runtime}")
                    else:
                        logger.info(t('automation_failed', error=str(result)))
                except Exception as e:
                    logger.info(t('automation_failed', error=str(e)))
            
            thread = threading.Thread(target=run_in_background)
            thread.daemon = True
            thread.start()
            
            self.send_json_response({"success": True, "message": t('automation_started')})
            
        except Exception as e:
            logger.error(f"启动自动化失败: {e}")
            self.send_error(500, f"启动自动化失败: {str(e)}")
    
    def handle_stop_automation(self):
        """停止SIMION自动化"""
        try:
            stop_simion_automation()
            self.send_json_response({"success": True, "message": "停止信号已发送"})
        except Exception as e:
            logger.error(f"停止自动化失败: {e}")
            self.send_error(500, f"停止自动化失败: {str(e)}")
    
    def send_json_response(self, data):
        """发送JSON响应"""
        self.send_response(200)
        self.send_header('Content-Type', 'application/json')
        self.send_header('Access-Control-Allow-Origin', '*')
        self.end_headers()
        
        response = json.dumps(data, ensure_ascii=False, indent=2)
        self.wfile.write(response.encode('utf-8'))
    
    def send_error(self, code, message):
        """发送错误响应"""
        self.send_response(code)
        self.send_header('Content-Type', 'application/json')
        self.send_header('Access-Control-Allow-Origin', '*')
        self.end_headers()
        
        error_response = json.dumps({
            "error": True,
            "code": code,
            "message": message
        }, ensure_ascii=False)
        self.wfile.write(error_response.encode('utf-8'))
    


class SimionServer:
    """SIMION服务器"""
    
    def __init__(self, host=None, port=None):
        self.host = host or SERVER_CONFIG['host']
        self.port = port or SERVER_CONFIG['port']
        self.server = None
        self.server_thread = None
    
    def start(self):
        """启动服务器"""
        try:
            self.server = HTTPServer((self.host, self.port), SimionAPIHandler)
            # 完全禁用HTTP服务器的日志输出
            self.server.log_message = lambda *args: None
            # 禁用服务器的所有日志记录
            logging.getLogger('http.server').disabled = True
            self.server_thread = threading.Thread(target=self.server.serve_forever)
            self.server_thread.daemon = True
            self.server_thread.start()
            
            print(f"Python后端服务器已启动: http://{self.host}:{self.port}")
            return True
        except Exception as e:
            logger.error(f"启动服务器失败: {e}")
            return False
    
    def stop(self):
        """停止服务器"""
        if self.server:
            self.server.shutdown()
            self.server.server_close()
            logger.info("Python后端服务器已停止")
    
    def is_running(self):
        """检查服务器是否运行"""
        return self.server_thread and self.server_thread.is_alive()


def main():
    """主函数"""
    # 加载环境变量配置
    load_from_env()
    
    server = SimionServer()
    
    # 设置信号处理器，确保Ctrl+C时能够强制清理
    def signal_handler(signum, frame):
        logger.info("收到中断信号 (Ctrl+C)，正在强制清理所有工作空间...")
        try:
            # 强制停止所有自动化任务
            stop_simion_automation()
            logger.info("所有任务已停止，工作空间已清理")
        except Exception as e:
            logger.error(f"强制清理失败: {e}")
        finally:
            server.stop()
            sys.exit(0)
    
    signal.signal(signal.SIGINT, signal_handler)
    signal.signal(signal.SIGTERM, signal_handler)
    
    if server.start():
        try:
            while True:
                time.sleep(1)
        except KeyboardInterrupt:
            logger.info("收到中断信号，正在停止服务器...")
        finally:
            server.stop()
    else:
        logger.error("服务器启动失败")
        return 1
    
    return 0


if __name__ == "__main__":
    exit(main())
